package main

import "fmt"

func main() {
	/*dll := NewDoubleLinkedList()

	dll.Insert(1)
	dll.Insert(1)
	dll.Insert(1)

	dll.Display() // Output: 1 2 3

	dll.Delete(1)

	dll.Display() // Output: 1 3

	dll.Update(3, 4)

	dll.Display() // Output: 1 4

	fmt.Println("Search 4:", dll.Search(4)) // Output: Search 4: true
	fmt.Println("Search 5:", dll.Search(5)) // Output: Search 5: false*/
}

type DNode struct {
	data interface{}
	prev *DNode
	next *DNode
}

// DoubleLinkedList 双向链表
type DoubleLinkedList struct {
	head *DNode
	tail *DNode
}

func NewDoubleLinkedList() *DoubleLinkedList {
	return &DoubleLinkedList{
		head: nil,
		tail: nil,
	}
}

//增加元素

func (dll *DoubleLinkedList) Insert(data interface{}) {
	newNode := &DNode{
		data: data,
		prev: nil,
		next: nil,
	}
	//没有元素,首尾相等
	if dll.head == nil {
		dll.head = newNode
		dll.tail = newNode
	} else {
		//现将node追加到最后一个节点上
		dll.tail.next = newNode
		//更新node的指针
		newNode.prev = dll.tail
		//更新链表的最后一个元素的值
		dll.tail = newNode
	}
}

func (dll *DoubleLinkedList) Delete(data interface{}) bool {
	current := dll.head
	for current != nil {
		//如果找到要删除的元素了
		if current.data == data {
			if current == dll.head && current == dll.tail {
				dll.head = nil
				dll.tail = nil
			} else if current == dll.head {
				dll.head = current.next
				dll.head.prev = nil
			} else if current == dll.tail {
				dll.tail = current.prev
				dll.tail.next = nil
			} else {
				current.prev.next = current.next
				current.next.prev = current.prev
			}
			return true
		}
		current = current.next
	}
	return false
}
func (dll *DoubleLinkedList) Update(oldData, newData interface{}) bool {
	current := dll.head
	for current != nil {
		if current.data == oldData {
			current.data = newData
			return true
		}
		current = current.next
	}
	return false
}

func (dll *DoubleLinkedList) Search(data interface{}) bool {
	current := dll.head
	for current != nil {
		if current.data == data {
			return true
		}
		current = current.next
	}
	return false
}

func (dll *DoubleLinkedList) Display() {
	current := dll.head
	for current != nil {
		fmt.Print(current.data, "")
		current = current.next
	}
	fmt.Println()
}
